package com.appengine.paranoid_android.lost;

import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.os.BatteryManager;
import android.os.Handler;
import android.os.Message;
import android.util.Log;

/**
 * Watches for updates that may be interesting to the keyguard, and provides
 * the up to date information as well as a registration for callbacks that care
 * to be updated.
 *
 * Note: this is mostly ripped verbatim from com.android.internal.policy.impl.KeyguardUpdateMonitor.
 */
public class LockScreenMonitor {
  private static final boolean DEBUG = true;
  private static final String TAG = "Info.LockScreenMonitor";

  private final Context mContext;
  private final Handler mHandler;

  private final LockScreen mScreen;

  // Messages for the handler.
  private static final int MSG_CONFIGURATION_CHANGED = 300;
  private static final int MSG_TIME_UPDATE = 301;
  private static final int MSG_BATTERY_UPDATE = 302;

  IntentFilter mFilter;
  BroadcastReceiver mReceiver;

  interface LockScreen {
    void onBatteryUpdate(int pluggedInStatus, int batteryLevel);
    void onTimeUpdate();
    void onConfigurationChange();
  }

  public LockScreenMonitor(Context context, LockScreen screen) {
    mContext = context;
    mScreen = screen;

    mHandler = new Handler() {
      @Override
      public void handleMessage(Message msg) {
        switch (msg.what) {
          case MSG_CONFIGURATION_CHANGED:
            handleConfigurationChange();
            break;
          case MSG_TIME_UPDATE:
            handleTimeUpdate();
            break;
          case MSG_BATTERY_UPDATE:
            handleBatteryUpdate(msg.arg1, msg.arg2);
            break;
        }
      }
    };

    mFilter = new IntentFilter();
    mFilter.addAction(Intent.ACTION_CONFIGURATION_CHANGED);
    mFilter.addAction(Intent.ACTION_TIME_TICK);
    mFilter.addAction(Intent.ACTION_TIME_CHANGED);
    mFilter.addAction(Intent.ACTION_BATTERY_CHANGED);
    mFilter.addAction(Intent.ACTION_TIMEZONE_CHANGED);

    mReceiver = new BroadcastReceiver() {
      @Override
      public void onReceive(Context context, Intent intent) {
        final String action = intent.getAction();
        if (DEBUG) Log.d(TAG, "received broadcast " + action);

        if (Intent.ACTION_CONFIGURATION_CHANGED.equals(action)) {
          mHandler.sendMessage(mHandler.obtainMessage(MSG_CONFIGURATION_CHANGED));
        } else if (Intent.ACTION_TIME_TICK.equals(action)
            || Intent.ACTION_TIME_CHANGED.equals(action)
            || Intent.ACTION_TIMEZONE_CHANGED.equals(action)) {
          mHandler.sendMessage(mHandler.obtainMessage(MSG_TIME_UPDATE));
        } else if (Intent.ACTION_BATTERY_CHANGED.equals(action)) {
          final int pluggedInStatus = intent.getIntExtra("status", BatteryManager.BATTERY_STATUS_UNKNOWN);
          int batteryLevel = intent.getIntExtra("level", 0);
          final Message msg = mHandler.obtainMessage(MSG_BATTERY_UPDATE,
                                                     pluggedInStatus,
                                                     batteryLevel);
          mHandler.sendMessage(msg);
        }
      }
    };
  }

  protected void handleBatteryUpdate(int pluggedInStatus, int batteryLevel) {
    mScreen.onBatteryUpdate(pluggedInStatus, batteryLevel);
  }

  protected void handleTimeUpdate() {
    mScreen.onTimeUpdate();
  }

  protected void handleConfigurationChange() {
    mScreen.onConfigurationChange();
  }

  public void registerReceiver() {
    mContext.registerReceiver(mReceiver, mFilter);
  }

  public void unregisterReceiver() {
    mContext.unregisterReceiver(mReceiver);
  }
}
